﻿//////////////////////////////////////////////////////////////////////////////
//
//  Copyright © 1998-2024 Glodon Company Limited.  All rights reserved.
//
//  Use of this software is subject to the terms of the Glodon license
//  agreement provided at the time of installation or download, or which
//  otherwise accompanies this software in either electronic or hard copy form.  
//
//////////////////////////////////////////////////////////////////////////////

#pragma once
#include "GcmpModelInterface.h"
#include "INoElementIdDbObject.h"

namespace gcmp
{
    /// \brief 元素标签组件
    /// 
    /// 每个元素有且只有一个标签组件。标签的存在主要有两个作用：
    /// 1) 给元素添加关键字，用极为简单的词语来说明内容的大意；
    /// 2) 用来在搜索时进行匹配。
    /// 和IElementAttributes不同的是，IElementAttributes是黑盒数据；而标签设计成白盒、结构化数据，在本地或者云端都能被搜索到。
    FINAL_INTERFACE class GCMP_MODEL_INTERFACE_EXPORT IElementTags : public INoElementIdDbObject
    {
        DEFINE_CAST_DERIVED(gcmp::IElementTags, gcmp::INoElementIdDbObject)
    public:
        /// \brief 是否存在tag
        /// \param key 名字
        /// \return 存在-true;不存在-false
        virtual bool HasTag(const std::wstring & key) const = 0;

        /// \brief 添加tag，值集合为空
        /// 
        /// \param key 名字
        /// \param 添加成功的-true;失败比如已经存在-false
        virtual bool AddTag(const std::wstring & key) = 0;

        /// \brief 删除tag
        /// \param key 名字
        /// \return 删除成功-true;失败比如不存在-false
        virtual bool RemoveTag(const std::wstring & key) = 0;

        /// \brief 查询tag中是否存在值
        /// \param key 名字
        /// \param textValue 值
        /// \return 存在-true;不存在-false
        virtual bool HasTagValue(const std::wstring & key, const std::wstring & textValue) const = 0;

        /// \brief 添加tag的值
        /// 
        /// 如果tag不存在，需要先添加tag
        /// \param key 名字
        /// \param textValue 值
        /// \param 添加成功-true;失败,比如tag不存在，或者textValue已经存在-false
        virtual bool AddTagValue(const std::wstring & key, const std::wstring & textValue) = 0;

        /// \brief 删除tag的值
        /// \param key 名字
        /// \param textValue 值
        /// \return 删除成功-true;失败比如key不存在或者textValue不存在-false
        virtual bool RemoveTagValue(const std::wstring & key, const std::wstring & textValue) = 0;

        /// \brief 获取tag的多值
        /// \param key 名字
        /// \return 值集合;如果不存在，返回nullptr
        virtual const std::set<std::wstring> * GetTagValues(const std::wstring & key) const = 0;

        /// \brief 获取tag的第一个值
        /// \param key 名字
        /// \return 值不少于1个时，返回第一个值;如果没有值，返回nullptr
        virtual const std::wstring * GetFirstTagValue(const std::wstring & key) const = 0;

        /// \brief 导出数据
        /// \return 导出的标签数据
        virtual std::map <std::wstring, std::set<std::wstring>> Export() const = 0;
    };
}
